/*******************************************************************************
 * Copyright (c) 2010 liw.
 * All rights reserved. 
 * 
 * This file is part of VanBus.
 * 
 *     VanBus is free software: you can redistribute it and/or modify
 *     it under the terms of the GNU General Public License as published by
 *     the Free Software Foundation, either version 3 of the License, or
 *     (at your option) any later version.
 * 
 *     VanBus is distributed in the hope that it will be useful,
 *     but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
 * 
 *     You should have received a copy of the GNU General Public License
 *     along with VanBus.  If not, see <http://www.gnu.org/licenses/>.
 * Contributors:
 *     liw - initial API and implementation
 ******************************************************************************/
package org.niclab.vanbus.query;

import java.util.ArrayList;

import org.niclab.vanbus.query.command.CommandChain;
import org.niclab.vanbus.query.command.ICommand;
import org.niclab.vanbus.query.command.ICommandChain;
import org.niclab.vanbus.query.handler.IProgressAware;
import org.niclab.vanbus.query.handler.IQueryHandler;

import android.content.Context;
import android.os.AsyncTask;
import android.util.Log;

public class SimpleQueryWorker extends AbstractQueryWorker{

	protected AsyncQueryTask asyncTask;
	protected CommandChain workerPostChain;
	
	private final String LOG_TAG="SimpleQueryWorker";

	
	/*public SimpleQueryWorker(Context ctx) {
		super(ctx);
		
	}*/
	
	/**
	 * this is gonna add the command to both synctask adn asynctask.
	 * but it will only be executed once when the worker's work is done.
	 * @param cmd the command to be added
	 */
	public void addWorkerPostCommand(ICommand cmd){
		addAsyncPostCommand(cmd);
		if(workerPostChain==null)
			workerPostChain = new CommandChain();
		workerPostChain.addCommand(cmd);	
	}
	
	public void addAsyncPostCommand(ICommand cmd) {
		createAsyncTask();
		this.asyncTask.addAsyncPostCommand(cmd);	
		
	}
	
	public void addAsyncPreCommand(ICommand cmd) {
		createAsyncTask();
		this.asyncTask.addAsyncPreCommand(cmd);
		
	}
	
	public void addAsyncProgressCommand(ICommand cmd){
		createAsyncTask();
		this.asyncTask.addAsyncProgressCommand(cmd);
	}

	
	public void createAsyncTask(){
		if(asyncTask==null)
			this.asyncTask=new AsyncQueryTask();
	}
	
	public AsyncTask getAsyncTask(){
		return asyncTask;
	}
	
	
	
	
	public void handleSyncQuery(){
		IQueryHandler sync = getSyncQueryHandler();
		Object result = null;
		if(sync!=null){
			executeSyncPreCommand();
			sync.query();
			executeSyncPostCommand(result);
		}
		
	}
	
	//this is gonna return an instance of this AsyncTask
	public void handleAsyncQuery(){
		
		IQueryHandler async = getAsyncQueryHandler();

		if(async!=null){
			
			if(asyncTask==null){
				this.createAsyncTask();
			}
			
			IQueryHandler handler = getAsyncQueryHandler();
			
			while(handler!=null){
				if(handler instanceof IProgressAware)
					((IProgressAware) handler).setAsyncQueryTask(asyncTask);
				handler = handler.getNextQueryHandler();
			}
		
			//async.query();
			asyncTask.execute(async);
			Log.d(LOG_TAG,"asyncTask started");
			
			
		}
		
		
	}
	private void executeWorkerPostCommand(){
		if(workerPostChain!=null)
			workerPostChain.execute(null);
	}
	
	@Override
	public void work() {
		
		handleSyncQuery();
		
		
		if(isWorkFinished()){
			executeWorkerPostCommand();
			return;
		}
		Log.v(LOG_TAG,"work isn't finished yet. Start AsynctTask");
		handleAsyncQuery();
			
	
		
	}

}
